package com.zhihuichongcheng.application.ui.main.fragment;

import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.support.annotation.NonNull;
import android.support.v7.widget.LinearLayoutManager;
import android.util.Pair;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.view.inputmethod.InputMethodManager;
import android.widget.FrameLayout;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;

import com.afollestad.materialdialogs.DialogAction;
import com.afollestad.materialdialogs.MaterialDialog;
import com.bumptech.glide.Glide;
import com.hyphenate.EMCallBack;
import com.hyphenate.EMConnectionListener;
import com.hyphenate.EMConversationListener;
import com.hyphenate.EMError;
import com.hyphenate.EMMessageListener;
import com.hyphenate.chat.EMClient;
import com.hyphenate.chat.EMConversation;
import com.hyphenate.chat.EMMessage;
import com.hyphenate.easeui.ui.EaseBaseFragment;
import com.jcodecraeer.xrecyclerview.XRecyclerView;
import com.smartlib.cmnObject.recycleView.OnItemLongClick;
import com.smartlib.cmnObject.recycleView.OnItemOnclick;
import com.smartlib.cmnObject.util.LogUtil;
import com.smartlib.cmnObject.util.SPUtil;
import com.zhihuichongcheng.application.R;
import com.zhihuichongcheng.application.glide.GlideCircleTransform;
import com.zhihuichongcheng.application.im.Constant;
import com.zhihuichongcheng.application.ui.im.activity.ChatActivity;
import com.zhihuichongcheng.application.ui.im.activity.ImContactActivity;
import com.zhihuichongcheng.application.ui.im.activity.ImSearchActivity;
import com.zhihuichongcheng.application.ui.im.activity.NewsActivity;
import com.zhihuichongcheng.application.ui.im.activity.NoticeActivity;
import com.zhihuichongcheng.application.ui.im.activity.UserListActivity;
import com.zhihuichongcheng.application.ui.im.adapter.EaseConversationAdapter;
import com.zhihuichongcheng.application.ui.mine.UserInfoActivity;
import com.zhihuichongcheng.application.ui.task.TaskListActivity;
import com.zhihuichongcheng.application.util.DialogUtils;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.Map;

/**
 * 消息页面 conversation list fragment
 */
public class ImFragment extends EaseBaseFragment
        implements OnClickListener, EMMessageListener {
    private final static int MSG_REFRESH = 2;
    protected boolean hidden;
    protected List<EMConversation> conversationList = new ArrayList<EMConversation>();
    protected XRecyclerView conversationListView;
    protected FrameLayout errorItemContainer;
    protected boolean isConflict;
    private TextView mTvSearch;
    private EaseConversationAdapter mAdapter;
    private ImageView mImContact, mImGroup, mImUser;
    private LinearLayout mLlNews, mLlNotice, mLlMettingNotice, mLlTasks;
    private SPUtil spUtil;
    protected Handler handler = new Handler() {
        public void handleMessage(android.os.Message msg) {
            switch (msg.what) {
                case 0:
                    onConnectionDisconnected();
                    String username = spUtil.getString("username");
                    String password = spUtil.getString("password");
                    EMClient.getInstance().login(username, password, new EMCallBack() {

                        @Override
                        public void onSuccess() {
                            EMClient.getInstance().groupManager().loadAllGroups();
                            EMClient.getInstance().chatManager().loadAllConversations();
                            EMClient.getInstance().addConnectionListener(connectionListener);
                        }

                        @Override
                        public void onError(int i, String s) {

                        }

                        @Override
                        public void onProgress(int i, String s) {

                        }
                    });
                    break;
                case 1:
//                ToastOpt.createToast(getContext(),"连接成功");
                    onConnectionConnected();
                    break;
                case MSG_REFRESH: {
                    conversationList.clear();
                    conversationList.addAll(loadConversationList());
                    if (mAdapter != null) {
                        mAdapter.setData(conversationList);
                        mAdapter.notifyDataSetChanged();
                    }
                    if (conversationListView != null) {
                        conversationListView.refreshComplete();
                        conversationListView.setNoMore(true);
                    }
                    break;
                }
                default:
                    break;
            }
        }
    };
    protected EMConversationListener convListener = new EMConversationListener() {

        @Override
        public void onCoversationUpdate() {
            refresh();
        }

    };
    protected EMConnectionListener connectionListener = new EMConnectionListener() {

        @Override
        public void onDisconnected(int error) {
            LogUtil.logD("error" + error);
            if (error == EMError.USER_REMOVED || error == EMError.USER_LOGIN_ANOTHER_DEVICE || error == EMError.SERVER_SERVICE_RESTRICTED) {
                isConflict = true;
            } else {
                handler.sendEmptyMessage(0);
            }
        }

        @Override
        public void onConnected() {

            handler.sendEmptyMessage(1);
        }
    };
    private TextView mTvCompanyNews, mTvNotice, mTvMettingNotice;
    private View mHeaderView;
    private boolean hasAddHeader = false;
    private ImageView mImCompanyNewsPoint, mImNoticePoint, mImMettingNoticePoint, mImCompanyNews, mImNotice, mImMettingNotice, mImTask;
    private EaseConversationListItemClickListener listItemClickListener;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        return inflater.inflate(R.layout.fragment_im, container, false);
    }

    @Override
    public void onActivityCreated(Bundle savedInstanceState) {
        if (savedInstanceState != null && savedInstanceState.getBoolean("isConflict", false))
            return;
        super.onActivityCreated(savedInstanceState);
        EMClient.getInstance().chatManager().addMessageListener(this);
    }

    @Override
    protected void initView() {
        mHeaderView = LayoutInflater.from(getContext()).inflate(R.layout.im_headview, conversationListView, false);
        mLlNews = (LinearLayout) mHeaderView.findViewById(R.id.ll_news);
        mLlNotice = (LinearLayout) mHeaderView.findViewById(R.id.ll_Notice);
        mLlMettingNotice = (LinearLayout) mHeaderView.findViewById(R.id.ll_mettingNotice);
        mLlTasks = (LinearLayout) mHeaderView.findViewById(R.id.ll_tasks);
        mImCompanyNewsPoint = (ImageView) mHeaderView.findViewById(R.id.im_companyNews_point);
        mImCompanyNews = (ImageView) mHeaderView.findViewById(R.id.im_companyNews);
        mImNoticePoint = (ImageView) mHeaderView.findViewById(R.id.im_Notice_point);
        mImNotice = (ImageView) mHeaderView.findViewById(R.id.im_Notice);
        mImMettingNoticePoint = (ImageView) mHeaderView.findViewById(R.id.im_mettingpoint_1);
        mImMettingNotice = (ImageView) mHeaderView.findViewById(R.id.im_metting_notice);
        mImTask = (ImageView) mHeaderView.findViewById(R.id.im_tasks);
        Glide.with(getContext()).load(R.drawable.ic_chat_news).transform(new GlideCircleTransform(getContext())).into(mImCompanyNews);
        Glide.with(getActivity()).load(R.drawable.ic_chat_notice).transform(new GlideCircleTransform(getActivity())).into(mImNotice);
        Glide.with(getActivity()).load(R.drawable.ic_chat_mettingnotice).transform(new GlideCircleTransform(getActivity())).into(mImMettingNotice);
        //新增代办任务入口
        Glide.with(getActivity()).load(R.drawable.ic_chat_tasks).transform(new GlideCircleTransform(getActivity())).into(mImTask);
        mTvCompanyNews = (TextView) mHeaderView.findViewById(R.id.tv_companyNews);
        mTvNotice = (TextView) mHeaderView.findViewById(R.id.tv_Notice);
        mTvMettingNotice = (TextView) mHeaderView.findViewById(R.id.tv_MettingNotice);
        mTvSearch = (TextView) mHeaderView.findViewById(R.id.tv_search);
        mImUser = (ImageView) getView().findViewById(R.id.im_user);
        mImGroup = (ImageView) getView().findViewById(R.id.im_chat_group);
        mImContact = (ImageView) getView().findViewById(R.id.im_chat_contact);
        inputMethodManager = (InputMethodManager) getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
        conversationListView = (XRecyclerView) getView().findViewById(R.id.list);

        errorItemContainer = (FrameLayout) mHeaderView.findViewById(R.id.fl_error_item);
        mImContact.setOnClickListener(this);
        mImGroup.setOnClickListener(this);
        mImUser.setOnClickListener(this);
        mTvSearch.setOnClickListener(this);
        mLlNews.setOnClickListener(this);
        mLlTasks.setOnClickListener(this);
        mLlNotice.setOnClickListener(this);
        mLlMettingNotice.setOnClickListener(this);

        conversationListView.setNoMore(true);
        conversationListView.setLoadingListener(new XRecyclerView.LoadingListener() {
            @Override
            public void onRefresh() {
                handler.postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        refresh();
                    }
                }, 500);
            }

            @Override
            public void onLoadMore() {

            }
        });
    }

    /**
     * refresh ui
     */
    public void refresh() {
        if (!handler.hasMessages(MSG_REFRESH)) {
            handler.sendEmptyMessage(MSG_REFRESH);
        }
    }

    @Override
    protected void setUpView() {
        conversationList.addAll(loadConversationList());
        conversationListView.setLayoutManager(new LinearLayoutManager(getContext()) {
            @Override
            public boolean canScrollVertically() {
                return super.canScrollVertically();
            }
        });
        mAdapter = new EaseConversationAdapter(getContext(), 0, conversationList);
        conversationListView.setAdapter(mAdapter);
        conversationListView.addHeaderView(mHeaderView);
        conversationListView.refreshComplete();
        mAdapter.setOnItemOnclick(new OnItemOnclick<EMConversation>() {
            @Override
            public void onClick(EMConversation emConversation, int position) {
                String username = emConversation.getUserName();
                if (username.equals(EMClient.getInstance().getCurrentUser()))
                    Toast.makeText(getContext(), R.string.Cant_chat_with_yourself, Toast.LENGTH_SHORT).show();
                else {
                    Intent intent = new Intent(getContext(), ChatActivity.class);
                    if (emConversation.isGroup()) {
                        if (emConversation.getType() == EMConversation.EMConversationType.ChatRoom) {
                            intent.putExtra(Constant.EXTRA_CHAT_TYPE, Constant.CHATTYPE_CHATROOM);
                        } else {
                            intent.putExtra(Constant.EXTRA_CHAT_TYPE, Constant.CHATTYPE_GROUP);
                        }

                    }
                    // it's single chat
                    intent.putExtra(Constant.EXTRA_USER_ID, username);
                    startActivity(intent);
                }
            }
        });

        mAdapter.setOnItemLongClick(new OnItemLongClick<EMConversation>() {
            @Override
            public boolean onClick(final EMConversation emConversation, int position) {
                if (null != emConversation) {
                    DialogUtils.showAlertDialog(getContext(), "确定删除?", new MaterialDialog.SingleButtonCallback() {
                        @Override
                        public void onClick(@NonNull MaterialDialog dialog, @NonNull DialogAction which) {
                            EMClient.getInstance().chatManager().deleteConversation(emConversation.conversationId(), true);
                            refresh();
                        }
                    });
                }
                return false;
            }
        });
        EMClient.getInstance().addConnectionListener(connectionListener);
        conversationListView.setOnTouchListener(new OnTouchListener() {

            @Override
            public boolean onTouch(View v, MotionEvent event) {
                hideSoftKeyboard();
                return false;
            }
        });
    }

    /**
     * load conversation list
     * @return +
     */
    protected List<EMConversation> loadConversationList() {
        // get all conversations
        Map<String, EMConversation> conversations = EMClient.getInstance().chatManager().getAllConversations();
        List<Pair<Long, EMConversation>> sortList = new ArrayList<Pair<Long, EMConversation>>();
        /**
         * lastMsgTime will change if there is new message during sorting
         * so use synchronized to make sure timestamp of last message won't change.
         */
        synchronized (conversations) {
            for (EMConversation conversation : conversations.values()) {
                if (conversation.getAllMessages().size() != 0) {
                    sortList.add(new Pair<Long, EMConversation>(conversation.getLastMessage().getMsgTime(), conversation));
                }
            }
        }
        try {
            // Internal is TimSort algorithm, has bug
            sortConversationByLastChatTime(sortList);
        } catch (Exception e) {
            e.printStackTrace();
        }
        List<EMConversation> list = new ArrayList<>();
        for (Pair<Long, EMConversation> sortItem : sortList) {
            list.add(sortItem.second);
        }
        return list;
    }

    protected void hideSoftKeyboard() {
        if (getActivity().getWindow().getAttributes().softInputMode != WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN) {
            if (getActivity().getCurrentFocus() != null)
                inputMethodManager.hideSoftInputFromWindow(getActivity().getCurrentFocus().getWindowToken(),
                        InputMethodManager.HIDE_NOT_ALWAYS);
        }
    }

    /**
     * sort conversations according time stamp of last message
     */
    private void sortConversationByLastChatTime(List<Pair<Long, EMConversation>> conversationList) {
        Collections.sort(conversationList, new Comparator<Pair<Long, EMConversation>>() {
            @Override
            public int compare(final Pair<Long, EMConversation> con1, final Pair<Long, EMConversation> con2) {

                if (con1.first.equals(con2.first)) {
                    return 0;
                } else if (con2.first.longValue() > con1.first.longValue()) {
                    return 1;
                } else {
                    return -1;
                }
            }

        });
    }

    /**
     * connected to server
     */
    protected void onConnectionConnected() {
        errorItemContainer.setVisibility(View.GONE);
    }

    /**
     * disconnected with server
     */
    protected void onConnectionDisconnected() {
        errorItemContainer.setVisibility(View.VISIBLE);
    }

    @Override
    public void onHiddenChanged(boolean hidden) {
        super.onHiddenChanged(hidden);
        this.hidden = hidden;
        if (!hidden && !isConflict) {
            refresh();
        }
    }

    @Override
    public void onResume() {
        super.onResume();
        if (!hidden) {
            refresh();
        }
        //判断是否点击了
        mImCompanyNewsPoint.setVisibility(View.GONE);
        mImNoticePoint.setVisibility(View.GONE);
        mImMettingNoticePoint.setVisibility(View.GONE);
        spUtil = SPUtil.getInstance(getContext());
        boolean valueNews = spUtil.getBoolean(getContext(), "news");
        boolean valueNotice = spUtil.getBoolean(getContext(), "notice");
        boolean valueMettingNotice = spUtil.getBoolean(getContext(), "mettingNotice");
        if (valueNews) {
            refulsh(1);
        }
        if (valueNotice) {
            refulsh(2);
        }
        if (valueMettingNotice) {
            refulsh(3);
        }

    }

    public void refulsh(int type) {
        switch (type) {
            case 1:
                mImCompanyNewsPoint.setVisibility(View.VISIBLE);
                break;
            case 2:
                mImNoticePoint.setVisibility(View.VISIBLE);
                break;
            case 3:
                mImMettingNoticePoint.setVisibility(View.VISIBLE);
                break;
        }
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        EMClient.getInstance().removeConnectionListener(connectionListener);
    }

    @Override
    public void onSaveInstanceState(Bundle outState) {
        super.onSaveInstanceState(outState);
        if (isConflict) {
            outState.putBoolean("isConflict", true);
        }
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.im_chat_contact:
                startActivity(ImContactActivity.class, null);
                break;
            case R.id.im_chat_group:
                startActivity(UserListActivity.class, null);
                break;
            case R.id.im_user:
                startActivity(UserInfoActivity.class, null);
                break;
            case R.id.tv_search:
                startActivity(ImSearchActivity.class, null);
                break;
            case R.id.ll_news:
//                Intent intent = new Intent(getActivity(), NewsActivity.class);
                spUtil.putBoolean(getContext(), "news", false);
                startActivity(NewsActivity.class, null);
                break;
            case R.id.ll_Notice:
                spUtil.putBoolean(getContext(), "notice", false);
                Bundle bundle = new Bundle();
                bundle.putString("title", "公告通知");

                startActivity(NoticeActivity.class, bundle);
                break;
            case R.id.ll_mettingNotice:
                spUtil.putBoolean(getContext(), "mettingNotice", false);
                bundle = new Bundle();
                bundle.putString("title", "会议通知");
                startActivity(NoticeActivity.class, bundle);
                break;
            case R.id.ll_tasks:
                bundle = new Bundle();
                bundle.putString("title", "任务");
                startActivity(TaskListActivity.class, bundle);
                break;
            default:
                break;
        }
    }

    public void startActivity(Class cls, Bundle bundle) {
        Intent intent = new Intent(getActivity(), cls);
        if (bundle != null) {
            intent.putExtras(bundle);
        }

        startActivity(intent);
        getActivity().overridePendingTransition(R.anim.push_left_in, R.anim.push_left_out);
    }

    @Override
    public void onMessageReceived(List<EMMessage> list) {
        refresh();
    }

    @Override
    public void onCmdMessageReceived(List<EMMessage> list) {

    }

    @Override
    public void onMessageReadAckReceived(List<EMMessage> list) {

    }

    @Override
    public void onMessageDeliveryAckReceived(List<EMMessage> list) {

    }

    @Override
    public void onMessageChanged(EMMessage emMessage, Object o) {

    }

    /**
     * set conversation list item click listener
     */
    public void setConversationListItemClickListener(EaseConversationListItemClickListener listItemClickListener) {
        this.listItemClickListener = listItemClickListener;
    }


    public interface EaseConversationListItemClickListener {
        /**
         * click event for conversation list
         * @param conversation -- clicked item
         */
        void onListItemClicked(EMConversation conversation);
    }


}
